package cate.game.role.farm.endless;

import cate.common.table.d.GDEndless;
import cate.common.table.d.GDFight;
import cate.common.table.d.GDFunc;
import cate.common.table.d.GDOperation;
import cate.common.table.farm.endless.EndlessCombatRow;
import cate.common.util.GameResult;
import cate.common.util.XT;
import cate.game.role.farm.endless.msg.*;
import cate.game.fight.task.FightTask;
import cate.game.play.part.FightSide;
import cate.game.play.proce.play.PlayPO;
import cate.game.res.MixRes;
import cate.game.role.Role;
import cate.game.role.farm.AbstractFarm;
import com.fasterxml.jackson.annotation.JsonIgnore;
import easy.java.dev.note.NoteClass;
import easy.java.dev.note.NoteField;
import easy.java.practice.errorcode.EcResult;
import org.apache.commons.lang3.StringUtils;

import java.util.HashMap;
import java.util.Map;

@NoteClass(value = "无尽轮回")
public class MyEndlessPO extends AbstractFarm {

    @NoteField(value = "本轮战斗们的记录")
    public EndlessCurCombats cur;

    @NoteField(value = "今天的挑战的起始关卡是第几关")
    public int combatNumStart = GDEndless.COMBAT_NUM_MIN;

    @NoteField(value = "今天本轮已挑战的关卡数最高值")
    public int combatCountMax;

    @NoteField(value = "最多通关到第几关", detail = "该功能的关卡数=波数，从1开始")
    public int combatNumPassed;

    @NoteField(value = "当前累计日常奖励", detail = "为null就表示无奖励可领取")
    public MixRes reward;

    @NoteField(value = "日常奖励领取到第几关的")
    public int rewardGotAt;

    @NoteField(value = "首通奖励领取记录")
    public Map<Integer, Boolean> rewardGot;

    @NoteField(value = "是否自动挑战")
    @JsonIgnore
    public volatile boolean autoEnter;

    @Override
    public void initialize(Role role) {
        super.initialize(role);
        if (cur == null) {
            cur = new EndlessCurCombats();
        }
        cur.initialize(role);
        if (rewardGot == null) {
            rewardGot = new HashMap<>();
        }
        FightTask task = role.getGame().fight.task.getTask(role, GDFunc.ENDLESS);
        if (task == null && !cur.needChoose) {
            combatsOver();
        }
    }

    @Override
    public int getFuncId() {
        return GDFunc.ENDLESS;
    }

    @Override
    public void onAfterOpen() {

    }

    public void onMergeSettle() {
        combatCountMax = 0;
        cur.reset(combatNumStart);
    }

    public void setCombatNumPassed(int value) {
        this.setCombatNumPassed(value, false);
    }
    /**
     * 设置最多通关到第几关
     *
     * @param forceSet 强制设置
     */
    public void setCombatNumPassed(int value, boolean forceSet) {
        if (forceSet || value > this.combatNumPassed) {
            this.combatNumPassed = value;
            role.getHistory().action.endlessCombatNum(combatNumPassed);
        }
    }

    @Override
    public int getFightFuncId() {
        return GDFunc.ENDLESS;
    }

    @Override
    public void offline() {
        if (cur.needChoose) {
            boolean chooseBuff = -1 == cur.buffOptionId;
            if (chooseBuff) {
                cur.setRandomBuffId();
            }
            if (cur.ing) {
                cur.setNeedChoose(false);
                challenge(chooseBuff);
            }
        }
    }

    @Override
    public void onDaySpan(boolean silence) {
        quit(false);
        combatNumStart = combatNumPassed - GDEndless.START_OFFSET;
        if (combatNumStart < GDEndless.COMBAT_NUM_MIN) {
            combatNumStart = GDEndless.COMBAT_NUM_MIN;
        }
        rewardGotAt = 0;
        reward = null;
        combatCountMax = 0;
        cur.reset(combatNumStart);
        noticeUpdate();
    }

    /** 通知客户端数据变更 */
    public void noticeUpdate() {
        role.sendNow(new EndlessDataResp(role));
    }

    public GameResult<Void> beginChallenge(int buffOptionId) {
        if (!role.getGame().farm.local.endless.canPlay()) {
            return new GameResult<Void>().fail("结算中，请稍后尝试");
        }
        if (buffOptionId <= 0 && !XT.isBlank(cur.optionIds)) {
            buffOptionId = cur.optionIds.get(0);
        }
        cur.buffOptionId = buffOptionId;
        cur.setNeedChoose(false);
        return challenge(true);
    }

    /** 进入战斗 */
    public GameResult<Void> challenge(boolean chooseBuff) {
        GameResult<Void> r = new GameResult<>();
        if (fighting) {
            return r.fail("当前战斗未结束");
        }
        if (cur.needChoose) {
            return r.fail("请先选择Buff");
        }
        EndlessCombatRow combatTpl = role.getGame().table.endless.combat.get(cur.combatNumTarget);
        if (combatTpl == null) {
            return r.fail("无法挑战当前层数");
        }
        // 判断前置条件
        EcResult<FightSide> fsRes = role.getGame().fight.side.createFightSideByCode(GDFight.Team.B, combatTpl.sideInstanceStr);
        if (!fsRes.ok()) {
            return r.fail(fsRes);
        }
        EndlessFTC context = new EndlessFTC(role);
        context.param = cur.getFightParam(chooseBuff);
        autoEnter = true;
        EcResult<PlayPO> fightRes = role.getGame().play.startByRole(role, context, fsRes.data);
        if (!fightRes.ok()) {
            return r.fail(fightRes);
        }
        this.fighting = true;
        noticeUpdate();
        role.sendNow(new EndlessChallengeResp(cur.combatNumTarget));
        return r.success();
    }

    /**
     * 退出战斗
     *
     * @param manual 是否是手动退出
     */
    public void quit(boolean manual) {
        this.autoEnter = false;
        FightTask task = role.getGame().fight.task.removeTask(role, GDFunc.ENDLESS);
        if (task != null) {
            if (!manual) {
                task.handleResultSelfThread(role);
                return;
            }
            this.endFighting();
        }
        this.combatsOver();
        noticeUpdate();
    }

    /** 一连串的战斗结束了 */
    public void combatsOver() {
        cur.reset(combatNumStart);
        autoEnter = false;
    }

    /**
     * 试图领取首通奖励
     *
     */
    public GameResult<Void> tryToGetFirstPassReward(int targetCombatNum) {
        GameResult<Void> r = new GameResult<>();
        if (targetCombatNum > this.combatNumPassed) {
            return r.fail("无法领取此关首通奖励");
        }
        if (rewardGot.containsKey(targetCombatNum)) {
            return r.fail("该奖励已领取");
        }
        EndlessCombatRow combatTpl = role.getGame().table.endless.combat.get(targetCombatNum);
        if (combatTpl == null || StringUtils.isBlank(combatTpl.rewardFirstPassStr)) {
            return r.fail("奖励不存在");
        }
        rewardGot.put(targetCombatNum, true);
        MixRes firstReward = new MixRes(combatTpl.rewardFirstPassStr);
        firstReward.add(role, true, GDOperation.ENDLESS_FIRST_PASS_REWARD);
        role.getGame().notice.dialogReward(role, firstReward);
        role.sendNow(new EndlessRewardFirstPassResp(targetCombatNum));
        return r.success();
    }

    /** 领取日常奖励 */
    public MixRes tryToGetReward() {
        MixRes r = this.reward;
        if (this.reward != null) {
            this.reward.add(role, true, GDOperation.ENDLESS_PASS_REWARD);
            this.reward = null;
            role.getHistory().action.endlessDailyReward();
        }
        return r;
    }

    public void gmJump(int level) {
        if (fighting || cur.ing) {
            role.getGame().notice.message(role, "请先结束战斗");
            return;
        }
        combatNumStart = level - 10;
        combatNumPassed = level;
        cur.reset(combatNumStart);
        noticeUpdate();
        role.getGame().notice.message(role, "跳关成功");
    }
}
